using AutoMapper;
using MediatR;
using ProduceBasicData.Api.Application.Command.WarehouseManage;
using ProduceBasicData.Domain.ProductionManage;
using ProduceBasicData.Domain.WarehouseManage;
using ProduceBasicData.Domain.WarehouseManage.WarehouseEnum;
using ProduceBasicData.ErrorCode;
using ProduceBasicData.Infrastructure.Interface;
using System;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;

namespace ProduceBasicData.Api.Application.Handler.WarehouseManage
{
    /// <summary>
    /// 更新出库单请求处理器
    /// </summary>
    public class OutWarehouseHandler : IRequestHandler<OutWarehouseCommand, ApiResult<int>>
    {
        private readonly IBaseRespository<StockOutOrder> _stockOutOrderRepository;
        private readonly IBaseRespository<StockOutOrderItem> _stockOutOrderItemRepository;
        private readonly IBaseRespository<Inventory> _inventoryRepository;
        private readonly IMapper _mapper;
        private readonly IBaseRespository<StockInOrderItem> itemrepo;
        private readonly IBaseRespository<Work_order> respository;

        public OutWarehouseHandler(IBaseRespository<StockOutOrder> stockOutOrderRepository,
                                  IBaseRespository<StockOutOrderItem> stockOutOrderItemRepository,
                                  IBaseRespository<Inventory> inventoryRepository,
                                  IMapper mapper,
                                  IBaseRespository<StockInOrderItem> itemrepo,
                                  IBaseRespository<Work_order > respository)
        {
            _stockOutOrderRepository = stockOutOrderRepository;
            _stockOutOrderItemRepository = stockOutOrderItemRepository;
            _inventoryRepository = inventoryRepository;
            _mapper = mapper;
            this.itemrepo = itemrepo;
            this.respository = respository;
        }

        /// <summary>
        /// 处理更新出库单请求
        /// </summary>
        public async Task<ApiResult<int>> Handle(OutWarehouseCommand request, CancellationToken cancellationToken)
        {
            try
            {
                // 获取出库单信息
                var stockOutOrder = await _stockOutOrderRepository.GetModelAsync(request.Id);
                if (stockOutOrder == null || stockOutOrder.Isdel)
                {
                    return new ApiResult<int>
                    {
                        Msg = "出库单不存在",
                        Code = ApiEnum.Failed
                    };
                }

                // 检查出库单当前状态
                if (stockOutOrder.Status == StockOutStatus.Completed)
                {
                    return new ApiResult<int>
                    {
                        Msg = "该出库单已完成出库",
                        Code = ApiEnum.Failed
                    };
                }

                if (stockOutOrder.Status == StockOutStatus.Cancelled)
                {
                    return new ApiResult<int>
                    {
                        Msg = "该出库单已取消",
                        Code = ApiEnum.Failed
                    };
                }

                // 开始事务处理
                using (var transaction = await _stockOutOrderRepository.DB.Database.BeginTransactionAsync(cancellationToken))
                {
                    try
                    {
                        // 获取出库单明细
                        var stockOutOrderItems = await _stockOutOrderItemRepository.GetAllAsync(item =>
                            item.StockOutOrderId == request.Id && !item.Isdel);

                        // 检查库存是否足够
                        foreach (var item in stockOutOrderItems)
                        {
                            // 使用AnyAsync优化库存检查，仅判断是否存在足够库存
                            var hasEnoughInventory = await itemrepo.AnyAsync(inv =>
                                inv.ActualQuantity>0);

                            // 库存不足处理（状态与前端对齐）
                            if (!hasEnoughInventory)
                            {
                                stockOutOrder.Status = StockOutStatus.Cancelled; // 假设枚举值3对应"数量不足"
                                await _stockOutOrderRepository.Update(stockOutOrder);
                                await transaction.CommitAsync();

                                return new ApiResult<int>
                                {
                                    Msg = $"物料{item.MaterialName}库存不足，无法完成出库",
                                    Code = ApiEnum.Failed
                                };
                            }
                        }

                       
                        stockOutOrder.Status = StockOutStatus.Completed;
                        stockOutOrder.ActualOutDate = DateTime.Now;

                        
                        await _stockOutOrderRepository.Update(stockOutOrder);

                        //// 扣减库存（按批次优先扣减）
                        //foreach (var item in stockOutOrderItems)
                        //{
                        //    // 按批次排序，优先扣减特定批次库存
                        //    var inventoryItems = await _inventoryRepository.GetAllAsync(inv =>
                        //        inv.MaterialId == item.MaterialId &&
                        //        inv.WarehouseId == stockOutOrder.WarehouseId &&
                        //        (inv.Quantity - inv.LockedQuantity) >= item.ActualQuantity);

                        //    // 按批次号升序排序（可根据实际业务调整排序规则）
                        //    var targetInventory = inventoryItems
                        //        .OrderBy(inv => inv.BatchNumber)
                        //        .FirstOrDefault();

                        //    if (targetInventory == null)
                        //    {
                        //        throw new Exception($"物料{item.MaterialName}库存记录异常，扣减失败");
                        //    }

                        //    // 执行库存扣减
                        //    targetInventory.Quantity -= item.ActualQuantity;
                        //    targetInventory.LastOutTime = DateTime.Now;
                        //    await _inventoryRepository.Update(targetInventory);
                        //}
                        //var mo = new Work_order();
                        //if (stockOutOrder.Status== StockOutStatus.Completed)
                        //{
                        //    mo.Status = 6;
                        //    await respository.Update(mo);
                        //}

                        var ins = _inventoryRepository.GetAll().Where(x=>!x.Isdel).ToList();
                        foreach (var item in ins)
                        {
                            item.Quantity = item.Quantity - Convert.ToDecimal( request.Num);
                        }
                        await _inventoryRepository.UpdateRange(ins);

                        

                        // 提交事务
                        await transaction.CommitAsync();

                        return new ApiResult<int>
                        {
                            Code = ApiEnum.Success,
                            Msg = "出库成功",
                            Data = stockOutOrder.Id
                        };
                    }
                    catch (Exception ex)
                    {
                        // 事务内异常直接处理并返回
                        await transaction.RollbackAsync();
                        return new ApiResult<int>
                        {
                            Code = ApiEnum.Failed,
                            Msg = $"出库处理失败：{ex.Message}",
                        };
                    }
                }
            }
            catch (Exception ex)
            {
                return new ApiResult<int>
                {
                    Code = ApiEnum.Failed,
                    Msg = $"出库操作异常：{ex.Message}",
                };
            }
        }
    }
}
